package proxydemo.factory;
import proxydemo.service.AInterface;


import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

/**
 * description
 *
 * @author Llx
 * @version v1.0.0
 * @since 2018/9/27
 */
public class FactoryPrx {

    public <T extends AInterface> T getSerivcePrx(Class<T> serviceCls) throws Exception{
        String serviceName = serviceCls.getSimpleName();
            return this.createIceProxy(serviceCls, serviceName);
    }


    private <T extends AInterface> T createIceProxy(Class<T> serviceCls, String systemName) throws Exception {

        InvocationHandler h =  new InvocationHandler() {
            int i = 0;
            @Override
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                AInterface t = serviceCls.newInstance();
                System.out.println(i);
                Object result = method.invoke(t, args);//执行目标对象的目标方法
                i++;
                System.out.println(i);
                return result;
            }
        };
        AInterface t = serviceCls.newInstance();

        Object o = Proxy.newProxyInstance(serviceCls.getClassLoader(), serviceCls.getInterfaces(), h);

        return (T)o;


    }
    private Object targetObject;//目标对象

    public Object createProxy() {
        ClassLoader loader = this.getClass().getClassLoader();
        Class[] interfaces = targetObject.getClass().getInterfaces();
        InvocationHandler h = new InvocationHandler() {
            @Override
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                Object result = method.invoke(targetObject, args);//执行目标对象的目标方法
                return result;
            }
        };
        Object proxyObject = Proxy.newProxyInstance(loader, interfaces, h);
        return proxyObject;
    }

    public Object getTargetObject() {
        return targetObject;
    }

    public void setTargetObject(Object targetObject) {
        this.targetObject = targetObject;
    }
}
